# -*- coding: utf-8 -*-
import datetime
from flask_restful import abort
from . import BaseCommon
from app.api.services import validator
from app.models.user import User, db
#from app.util.Sms import send_sms


class ServiceUser(BaseCommon):

	def __init__(self):
		super(ServiceUser, self).__init__()

	def get_users(self):
		users = User.query.all()
		if len(users) == 0:
			return {"errcode": 200, "errmsg": "ok", "data": []}
		brr = [self.obj_to_view(u, {"id", "username", "email", "nickname", "mobile", "role_type", "avatar", "openid",
									"unionid", "gender", "created_at", "updated_at"}) for u in users]
		return {"errcode": 200, "errmsg": "ok", "data": brr}

	def get_user(self, user_id):
		user = User.query.filter_by(id=user_id).first()
		return {"errcode": 200, "errmsg": "ok", "data": self.obj_to_view(user, {
			"avatar", "username", "nickname", "mobile", "role_type"})}

	def auth_token(self, token):
		user = User.verify_auth_token(token)
		if user:
			data = {"errcode": 200, "errmsg": "ok", "id": user.id, "username": user.username,
					"role_type": user.role_type}
			return data
		return {"errcode": 404, "errmsg": "Token is error"}

	def auth_jwt_token(self, token):
		data = self.decode(token)
		if "id" in data:
			user = User.query.filter_by(id=data["id"]).first()
			data["user"] = self.obj_to_view(user,
											{"avatar", "username", "nickname", "mobile", "role_type", "workflow_state"})
			return {"errcode": 200, "errmsg": "ok", "data": data}
		return {"errcode": 400, "errmsg": data}

	def auth_refresh_token(self, token):
		data = self.refresh_decode(token)
		if data:
			user = User.query.filter_by(id=data["id"]).first()
			data = self.encode({"id": user.id})
			data["user"] = self.obj_to_view(user,
											{"avatar", "username", "nickname", "mobile", "role_type", "workflow_state"})
			return {"errcode": 200, "errmsg": "ok", "data": data}
		return {"errcode": 403, "errmsg": "refresh_token Has expired, please re-login"}

	def auth_login(self, username, password):
		login_type = validator.validate_login_user(username)
		if login_type == "email":
			user = self.get_user_by_email(username)
			response = validator.validate_login_password(user, password)
		elif login_type == "mobile":
			user = self.get_user_by_mobile(username)
			response = validator.validate_login_password(user, password)
		else:
			return {"errcode": 404, "errmsg": "user is not exit"}
		if response["errcode"] == 200:
			data = self.encode({"id": user.id})
			data["id"] = user.id
			data["role_type"] = user.role_type
			data["username"] = user.username
			return {"errcode": 200, "errmsg": "ok", "data": data}
		return response

	def auth_login_wx(self, userInfo):
		user = User.is_exist({"openid": userInfo["openid"]})
		print("user=", user)
		if "unionid" not in userInfo:
			userInfo["unionid"] = ''
		if user:
			user.city = userInfo["city"]
			user.nickname = userInfo["nickName"]
			user.avatar = userInfo["avatarUrl"]
			user.openid = userInfo["openid"]
			if userInfo["unionid"] not in ['', None]:
				user.unionid = userInfo["unionid"]
			msg = "update ok"
		else:
			_user = {
				"mobile": datetime.datetime.now().strftime("%Y%m%d%H%M%S%f"),
				"passwd": datetime.datetime.now().strftime("%Y%m%d"),
				"nickname": userInfo["nickName"],
				"username": userInfo["nickName"],
				"city": userInfo["city"],
				"avatar": userInfo["avatarUrl"],
				"openid": userInfo["openid"],
				"unionid": userInfo["unionid"]
			}
			user = User(**_user)
			msg = "new ok"
		db.session.add(user)
		try:
			db.session.commit()
		except Exception as e:
			return {"errcode": 404, "errmsg": "error"}
		data = self.encode({"id": user.id})
		data["id"] = user.id
		data["mobile"] = ""
		if validator.validate_mobile(user.mobile):
			data["mobile"] = user.mobile
		return {"errcode": 200, "errmsg": msg, "data": data}

	def get_user_by_id(self, id):
		return User.query.filter_by(id=int(id)).first()

	def get_user_by_email(self, email):
		return User.query.filter_by(email=email).first()

	def get_user_by_mobile(self, mobile):
		return User.query.filter_by(mobile=mobile).first()

	def batch_users(self, data):
		"""
		:param data: [{},{},....]
		:return:
		"""
		if len(data) == 0:
			return {"errcode": 400, "errmsg": "insert user data is not null"}
		users = []
		for d in data:
			user = User(**d)
			users.append(user)
		if len(users) > 0:
			db.session.add_all(users)
			return {"errcode": 200, "errmsg": "ok"}
		return {"errcode": 400, "errmsg": "insert user data is not null"}

	def add_user(self, data):
		"""
		:param data:
		:return:
		"""
		return User.insert_admin_user(data)

	def edit_user(self, data, **temp):
		"""
		:param data:
		:return:
		"""
		if not data:
			abort(406, message="nothing to update")
		_data = validator.DataValidator.filter_key_value(data)
		user = User.query.filter_by(**temp).update(_data)
		if not user:
			abort(406, message="update user error")
		return {"errcode": 200, "errmsg": "update ok"}

	def update_role(self, **temp):
		"""
		:param data:
		:return:
		"""
		data = validator.DataValidator.filter_key_value(temp)
		if not data:
			abort(406, message="nothing to update")
		_data = validator.DataValidator.filter_key_value(data)
		user = User.query.filter_by(**temp).update(_data)
		if not user:
			abort(406, message="update user error")
		return {"errcode": 200, "errmsg": "update ok"}

	def delete_user(self, **temp):
		res = User.query.filter_by(**temp).delete(synchronize_session=False)
		if not res:
			abort(406, message="delete user {}".format(temp))
		return {"errcode": 200, "errmsg": "delete ok"}

	def auth_phone(self, phone):
		return send_sms(phone)

	def bind_phone(self, temp):
		user = User.is_exist({"mobile": temp["mobile"]})
		if user and user.id == int(temp["id"]):
			return {"errcode": 400, "errmsg": "已经绑定过了"}
		elif user and user.id != int(temp["id"]):
			return {"errcode": 400, "errmsg": "该手机号已经被其他用户绑定"}
		else:
			user = User.query.filter_by(**{"id": int(temp["id"])})
			if not user.first():
				abort(406, message="binding mobile error")
			user = user.first()
		if validator.validate_mobile(user.mobile):
			return {"errcode": 404, "errmsg": "用户已经绑定过号码{}".format(user.mobile)}
		user.mobile = temp["mobile"]
		db.session.add(user)
		try:
			db.session.commit()
		except Exception as e:
			return {"errcode": 404, "errmsg": "error"}
		return {"errcode": 200, "errmsg": "ok"}

	def update_bind_phone(self, temp):
		user = User.is_exist({"mobile": temp["mobile"]})
		if user and user.id != int(temp["id"]):
			return {"errcode": 400, "errmsg": "该手机号已经被其他用户绑定"}
		if user and user.id == int(temp["id"]):
			user.mobile = temp["mobile"]
			db.session.add(user)
			try:
				db.session.commit()
			except Exception as e:
				return {"errcode": 404, "errmsg": "error"}
		return {"errcode": 200, "errmsg": "ok"}
